home *** CD-ROM | disk | FTP | other *** search
/ Info-Mac 3 / Info_Mac_1994-01.iso / Development / Source / Macintosh Tracker 1.1 Source / Tracker Server Folder / automaton.c < prev    next >
Text File  |  1993-05-18  |  5KB  |  214 lines

  1. /* automaton.c */
  2.  
  3. /* $Id: automaton.c,v 3.8 1993/01/16 17:00:27 espie Exp espie $
  4.  * $Log: automaton.c,v $
  5.  * Revision 3.8  1993/01/16  17:00:27  espie
  6.  * Corrected stupid bug (run_in_fg)
  7.  *
  8.  * Revision 3.7  1993/01/15  14:00:28  espie
  9.  * Added bg/fg test.
  10.  *
  11.  * Revision 3.6  1992/11/27  10:29:00  espie
  12.  * General cleanup
  13.  *
  14.  * Revision 3.5  1992/11/24  10:51:19  espie
  15.  * un#ifdef'ed showseq code.
  16.  *
  17.  * Revision 3.4  1992/11/23  10:12:23  espie
  18.  * *** empty log message ***
  19.  *
  20.  * Revision 3.3  1992/11/22  17:20:01  espie
  21.  * Simplified delay_pattern.
  22.  *
  23.  * Revision 3.2  1992/11/20  14:53:32  espie
  24.  * Added finetune.
  25.  *
  26.  * Revision 3.1  1992/11/19  20:44:47  espie
  27.  * Protracker commands.
  28.  *
  29.  * Revision 3.0  1992/11/18  16:08:05  espie
  30.  * New release.
  31.  *
  32.  * Revision 2.16  1992/11/17  17:15:37  espie
  33.  * New output for new interface
  34.  * Modified repeat logic: now works irregardless of repeat points.
  35.  * start
  36.  *
  37.  * Revision 2.8  1992/07/14  14:23:41  espie
  38.  * Changed fine speed command and comments.
  39.  * Added two level of fault tolerancy.
  40.  */
  41.      
  42.  
  43. #include <stdio.h>
  44. #include <stdlib.h>
  45. #include <string.h>
  46.      
  47. #include "defs.h"
  48. #include "extern.h"
  49. #include "song.h"
  50. #include "channel.h"
  51.      
  52. LOCAL char *id = "$Id: automaton.c,v 3.8 1993/01/16 17:00:27 espie Exp espie $";
  53. LOCAL BOOL show;
  54.      
  55. /* updates the pattern to play in the automaton.
  56.  * Checks that the pattern actually exists.
  57.  */
  58. LOCAL void set_pattern(a)
  59. struct automaton *a;
  60.     {
  61.     int p;
  62.     if (a->pattern_num >= a->info->length)
  63.         {
  64.         error = UNRECOVERABLE;
  65.         return;
  66.         }
  67.  
  68.     if (run_in_fg())
  69.         {
  70.         if (show)
  71.             printf("\n%3d\n", a->pattern_num);
  72.         else
  73.             printf("%3d/%3d\b\b\b\b\b\b\b", a->pattern_num, a->info->length);
  74.         fflush(stdout); 
  75.         }
  76.         /* there is a level of indirection in the format,
  77.          * i.e., patterns can be repeated.
  78.          */
  79.     p = a->info->patnumber[a->pattern_num];
  80.     a->gonethrough[a->pattern_num] = TRUE;
  81.     if (p >= a->info->maxpat)
  82.         {
  83.         error = UNRECOVERABLE;
  84.         return;
  85.         }
  86.     a->pattern = a->info->pblocks + p;
  87.     }
  88.  
  89. LOCAL void clear_repeats(a, from, upto)
  90. struct automaton *a;
  91. int from, upto;
  92.     {
  93.     int i;
  94.  
  95.     for (i = from; i <= upto; i++)
  96.         a->gonethrough[i] = FALSE;
  97.     }
  98.  
  99. LOCAL void reset_repeats(a)
  100. struct automaton *a;
  101.     {
  102.     clear_repeats(a, 0, a->info->length);
  103.     a->gonethrough[a->info->length] = TRUE;
  104.     }
  105.  
  106. /* initialize all the fields of the automaton necessary
  107.  * to play a given song.
  108.  */
  109. void init_automaton(a, song, start, s)
  110. struct automaton *a;
  111. struct song *song;
  112. int start;
  113. BOOL s;
  114.     {
  115.     a->info = &song->info;
  116.     a->pattern_num = start;     /* first pattern */
  117.     show = s;
  118.  
  119.     a->loop_pattern_num = 0;
  120.     a->loop_note_num = 0;
  121.     a->loop_counter = 0;
  122.  
  123.     reset_repeats(a);
  124.  
  125.     a->note_num = 0;        /* first note in pattern */
  126.     a->counter = 0;         /* counter for the effect tempo */
  127.     a->speed = NORMAL_SPEED;/* this is the default effect tempo */
  128.     a->finespeed = NORMAL_FINESPEED;    
  129.                             /* this is the fine speed (100%=NORMAL_FINESPEED) */
  130.     a->do_stuff = DO_NOTHING;   
  131.                             /* some effects affect the automaton,
  132.                              * we keep them here.
  133.                              */
  134.  
  135.     error = NONE;           /* Maybe we should not reset errors at
  136.                              * this point.
  137.                              */
  138.     set_pattern(a);
  139.     }
  140.  
  141. /* Gets to the next pattern, and displays stuff */
  142. LOCAL void advance_pattern(a)
  143. struct automaton *a;
  144.     {
  145.     if (run_in_fg() && show)
  146.         printf("\n\n");
  147.     if (++a->pattern_num >= a->info->length)
  148.         a->pattern_num = 0;
  149.     if (a->gonethrough[a->pattern_num])
  150.         {
  151.         error = ENDED;
  152.         reset_repeats(a);
  153.         }
  154.     set_pattern(a);
  155.     a->note_num = 0;
  156.     }
  157.  
  158.         
  159.  
  160. /* process all the stuff which we need to advance in the song,
  161.  * including set_speed, set_skip and set_fastskip.
  162.  */
  163. void next_tick(a)
  164. struct automaton *a;
  165.     {
  166.     if (a->do_stuff & SET_SPEED && a->new_speed)
  167.         {
  168.             /* there are three classes of speed changes:
  169.              * 0 does nothing. (should stop)
  170.              * <32 is the effect speed (resets the fine speed).
  171.              * >=32 changes the finespeed, default 125
  172.              */
  173.         if (a->new_speed >= 32)
  174.             a->finespeed = a->new_speed;
  175.         else if (a->new_speed)
  176.             {
  177.             a->speed = a->new_speed;
  178.             a->finespeed = NORMAL_FINESPEED;
  179.             }
  180.         }
  181.     if (++a->counter >= a->speed)
  182.         {
  183.         a->counter = 0;
  184.         if (run_in_fg() && show)
  185.             printf("\n");
  186.         if (a->do_stuff & JUMP_PATTERN)
  187.             {
  188.             clear_repeats(a, a->loop_pattern_num, a->pattern_num);
  189.             a->pattern_num = a->loop_pattern_num;
  190.             set_pattern(a);
  191.             a->note_num = a->loop_note_num;
  192.             }
  193.         else if (a->do_stuff & SET_FASTSKIP)
  194.             {
  195.             a->pattern_num = a->new_pattern;
  196.             set_pattern(a);
  197.             a->note_num = 0;
  198.             }
  199.         else if (a->do_stuff & SET_SKIP)
  200.             {
  201.             advance_pattern(a);
  202.             a->note_num = a->new_note;
  203.             }
  204.         else
  205.             {
  206.             if (++a->note_num >= BLOCK_LENGTH)
  207.                 advance_pattern(a);
  208.             }
  209.         a->do_stuff = DO_NOTHING;
  210.         }
  211.     }
  212.  
  213.  
  214.